package com.ytjj.qmyx.data.service.impl;

import com.alibaba.druid.util.StringUtils;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.ytjj.common.constants.SysConfigConstants;
import com.ytjj.common.utils.Aes128CBCUtil;
import com.ytjj.common.utils.DateTimeUtil;
import com.ytjj.common.utils.HttpClientUtil;
import com.ytjj.common.utils.feishu.FeiShuUtil;
import com.ytjj.qmyx.data.mapper.SmsSenderRecordsDao;
import com.ytjj.qmyx.data.model.*;
import com.ytjj.qmyx.data.service.MsgService;
import com.ytjj.qmyx.mall.mapper.MsgFailLogMapper;
import com.ytjj.qmyx.mall.model.MsgFailLog;
import com.ytjj.qmyx.mall.model.MsgFailLogExample;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import org.springframework.util.CollectionUtils;

import javax.annotation.Resource;
import java.util.*;

/**
 *
 * 
 * @describe
 */
@Slf4j
@Service
public class MsgServiceImpl implements MsgService {

    @Resource
    private MsgFailLogMapper msgFailLogMapper;
    @Resource
    private SmsSenderRecordsDao smsSenderRecordsDao;

    /**
     * 短链域名
     * 存在多选的情况
     * 15：g3v.cn-XXXX优品
     */
    @Value("${shortSms.domain:15}")
    private String domain;

    @Value("${shortSms.key:}")
    private String key;

    @Value("${shortSms.url:}")
    private String url;

    /**
     * 短链平台接口url
     */
    @Value("${short.platform.url:}")
    private String platformUrl;

    /**
     * 短链平台接口域名
     */
    @Value("${short.platform.domain:}")
    private String platformDomain;

    @Override
    public String generateLongUrl(String longUrl, String phone, String orderSource,String token,String channel) {
        String key = "eCcgc+=F'=M)$+'+";
        String iv = "g&_&J{~mK~e#h_Y2";
        String md5_phone = null;
        try {
            md5_phone = Aes128CBCUtil.encrypt(phone, key, iv);
        } catch (Exception e) {
            e.printStackTrace();
        }
        if (org.springframework.util.StringUtils.isEmpty(md5_phone)) {
            return null;
        }
        if (!longUrl.contains("?")) {
            longUrl = longUrl + "?serialNumber=";
        }else {
            longUrl = longUrl + "&serialNumber=";
        }
        md5_phone = md5_phone.replaceAll("\\+", "%2B");
        md5_phone = md5_phone.replaceAll("=", "%3D");
        md5_phone = md5_phone.replaceAll("/", "%2F");
        longUrl = longUrl + md5_phone;
        if (!StringUtils.isEmpty(orderSource)) {
            if ("android".equals(orderSource.toLowerCase())
                    || "ios".equals(orderSource.toLowerCase())
                    || "app".equals(orderSource.toLowerCase())) {
                longUrl = longUrl + "&orderSource=app";
            }else if (orderSource.startsWith("ISV") || orderSource.startsWith("weapp")) {
                longUrl = longUrl + "&orderSource=weapp";
            }else {
                longUrl = longUrl + "&orderSource=h5";
            }
        }
        if(!StringUtils.isEmpty(token)){
            longUrl = longUrl + "&token="+token;
        }
        if(!StringUtils.isEmpty(channel)){
            longUrl = longUrl + "&channel="+channel;
        }
        return longUrl;
    }

    @Override
    public String generaterShortUrl(List<String> handleLongUrls) {
        long curTimeMillis = System.currentTimeMillis();
        System.out.println("====短链接口开始====" + curTimeMillis);
        System.out.println("====短链接口开始====" + curTimeMillis);
        Map<String, String> map = new HashMap<String, String>();
        map.put("url", handleLongUrls.get(0));
        map.put("format", "json");
        map.put("key", key);
        map.put("expireDate", DateTimeUtil.addtime(DateTimeUtil.DateToStr(new Date()),30*24*60));
        map.put("domain", domain);
        log.info("====短链接口开始参数:{}====", JSONObject.toJSONString(map));
        String result = HttpClientUtil.doGet(url, map);
        log.info("====短链接口结束返回:{}====",result);
        Map resultMap = JSONObject.parseObject(result, Map.class);
        String code = String.valueOf(resultMap.getOrDefault("code", ""));
        String err = String.valueOf(resultMap.getOrDefault("err", ""));
        String url = String.valueOf(resultMap.getOrDefault("url", ""));
        url = url.replace("http://", "");
        url = url.replace("https://", "");
        if (!"0".equals(code)) {
            log.info("====批量生成短链失败===code:{},msg:{}", code, err);
            return null;
        }
        return  url;
    }

    @Override
    public String longToShortUrl(String handleLongUrl) {
        log.info("====短链接口开始，长链：" + handleLongUrl);
        //时间累计
        Calendar gc = new GregorianCalendar();
        gc.setTime(new Date());
        //失效时间为1年
        gc.add(GregorianCalendar.MINUTE, 365*24*60);
        DlListVo dlListVo = new DlListVo();
        dlListVo.setUrl(handleLongUrl);
        dlListVo.setDomain(platformDomain);
        dlListVo.setForever(0);
        dlListVo.setExpirationDate(gc.getTime());
        dlListVo.setTitle("API生成");
        String resultJson = HttpClientUtil.doPostJson(platformUrl + "/admin/longToShort", JSON.toJSONString(dlListVo));
        DlListVo respVo = JSON.parseObject(resultJson, DlListVo.class);
        String urlShort = "";
        if(null != respVo && !StringUtils.isEmpty(respVo.getUrlShort())){
            urlShort = respVo.getUrlShort();
        }else {//生成失败，使用三维推短链生成
            urlShort = generaterShortUrl(Arrays.asList(handleLongUrl));
        }
        log.info("====自有平台短链解析实体====" + resultJson);
        return urlShort;
    }

    @Override
    public void saveMsgFailLog(String result_sto, String channelMark, byte type, String phone, String content,String sign,Integer orderId) {
        try {
            MsgFailLog msgFailLog = new MsgFailLog();
            msgFailLog.setStatus((byte)0);
            if(SysConfigConstants.XINYICHEN.equals(channelMark)){
                msgFailLog.setSmsSource(1);
            }else if(SysConfigConstants.SANTONG.equals(channelMark)){
                msgFailLog.setSmsSource(2);
            }else if(SysConfigConstants.MENGWANG.equals(channelMark)){
                msgFailLog.setSmsSource(3);
            }else {
                msgFailLog.setSmsSource(0);
            }

            if (StringUtils.isEmpty(result_sto)) {
                msgFailLog.setStatus((byte) 1);
            } else {
                if (SysConfigConstants.SANTONG.equals(channelMark)) {
                    SanTongResponse sanTongResponse = JSONObject.parseObject(result_sto, SanTongResponse.class);
                    msgFailLog.setSmsId(sanTongResponse.getMsgid());
                    if (!"0".equals(sanTongResponse.getResult())) {
                        msgFailLog.setStatus((byte) 1);
                        msgFailLog.setMessage(sanTongResponse.getDesc());
                    }
                } else if (SysConfigConstants.XINYICHEN.equals(channelMark)) {
                    XinycSmsResponse response = JSONObject.parseObject(result_sto, XinycSmsResponse.class);
                    msgFailLog.setSmsId(Optional.ofNullable(response.getData()).orElse("").toString());
                    if(0 != response.getStatus()){
                        msgFailLog.setStatus((byte) 1);
                        msgFailLog.setMessage(response.getMessage());
                    }
                } else if (SysConfigConstants.MENGWANG.equals(channelMark)) {
                    MengWangResponse response = JSONObject.parseObject(result_sto, MengWangResponse.class);
                    msgFailLog.setSmsId(response.getMsgid());
                    if(!"0".equals(response.getResult())){
                        msgFailLog.setStatus((byte) 1);
                        msgFailLog.setMessage(response.getDesc());
                    }
                }
            }
            msgFailLog.setType(type);
            msgFailLog.setCreateTime(new Date());
            msgFailLog.setPhone(phone);
            msgFailLog.setContent(sign + content);
            msgFailLog.setRespText(result_sto);
            msgFailLogMapper.insertSelective(msgFailLog);
            //短信来自后台发送，需要更新发送记录表
            if("8".equals(String.valueOf(type))){
                Integer id = msgFailLog.getId();
                smsSenderRecordsDao.updateById(orderId,id);
            }
            log.info("====已记录短信到日志表====");
        } catch (Exception e) {
            log.error("====记录短信日志出错：{}",e);
            FeiShuUtil.sendMsg(String.format("记录短信日志出错：%s",e.getMessage()));
        }
    }

    @Override
    public void updateXinycMsgInfo(List<XinycSmsRequest> request) {
        log.info("===xinyichen回调Response==="+ JSON.toJSONString(request));
        if(CollectionUtils.isEmpty(request)){
            return;
        }
        request.forEach(e->{
            try {
                String smsId = e.getSmsId();
                if(!StringUtils.isEmpty(smsId)){
                    Integer status = e.getStatus();
                    MsgFailLogExample example = new MsgFailLogExample();
                    example.createCriteria().andSmsIdEqualTo(smsId).andStatusNotEqualTo((byte)2);
                    MsgFailLog msgFailLog = new MsgFailLog();
                    msgFailLog.setStatus(status == 0 ? (byte) 2 : (byte) 3);
                    msgFailLog.setMessage(!StringUtils.isEmpty(e.getDesc()) ? e.getDesc() : null);
                    msgFailLog.setCode(!StringUtils.isEmpty(e.getCode()) ? e.getCode() : null);
                    msgFailLog.setRespText(JSON.toJSONString(e));
                    msgFailLog.setReportTime(DateTimeUtil.StrToTime(e.getReportTime()));
                    msgFailLogMapper.updateByExampleSelective(msgFailLog,example);
                }
            } catch (Exception ex) {
                FeiShuUtil.sendMsg(String.format("xinyichen通道短信发送后回调更新本地短信日志出错：%s",ex.getMessage()));
                log.error("xinyichen通道短信发送后回调更新本地短信日志出错：{}",ex);
            }
        });
    }

    @Override
    public void updateSanTongMsgInfo(List<SanTongRequestVo> requestVos) {
        log.info("===sanTong回调Response==="+JSON.toJSONString(requestVos));
        requestVos.forEach(e->{
            try {
                String smsId = e.getMsgid();
                if(!StringUtils.isEmpty(smsId)){
                    Integer status = e.getStatus();
                    MsgFailLogExample example = new MsgFailLogExample();
                    example.createCriteria().andSmsIdEqualTo(smsId).andStatusNotEqualTo((byte)2);
                    MsgFailLog msgFailLog = new MsgFailLog();
                    msgFailLog.setStatus(status == 0 ? (byte) 2 : (byte) 3);
                    msgFailLog.setMessage(!StringUtils.isEmpty(e.getDesc()) ? e.getDesc() : null);
                    msgFailLog.setCode(!StringUtils.isEmpty(e.getWgcode()) ? e.getWgcode() : null);
                    msgFailLog.setRespText(JSON.toJSONString(e));
                    msgFailLog.setReportTime(DateTimeUtil.StrToTime(e.getTime()));
                    msgFailLogMapper.updateByExampleSelective(msgFailLog,example);
                }
            } catch (Exception ex) {
                FeiShuUtil.sendMsg(String.format("santong通道短信发送后回调更新本地短信日志出错：%s",ex.getMessage()));
                log.error("santong通道短信发送后回调更新本地短信日志出错：{}",ex);
            }
        });
    }

    @Override
    public void updateMengWangMsgInfo(List<MengWangRequestVo> requestVos) {
        log.info("===mengwang回调Response==="+JSON.toJSONString(requestVos));
        requestVos.forEach(e->{
            try {
                String smsId = e.getMsgid();
                if(!StringUtils.isEmpty(smsId)){
                    Integer status = e.getStatus();
                    MsgFailLogExample example = new MsgFailLogExample();
                    example.createCriteria().andSmsIdEqualTo(smsId).andStatusNotEqualTo((byte)2);
                    MsgFailLog msgFailLog = new MsgFailLog();
                    msgFailLog.setStatus(status == 0 ? (byte) 2 : (byte) 3);
                    msgFailLog.setMessage(!StringUtils.isEmpty(e.getErrdesc()) ? e.getErrdesc() : null);
                    msgFailLog.setCode(!StringUtils.isEmpty(e.getErrcode()) ? e.getErrcode() : null);
                    msgFailLog.setRespText(JSON.toJSONString(e));
                    msgFailLog.setReportTime(DateTimeUtil.StrToTime(e.getRtime()));
                    msgFailLogMapper.updateByExampleSelective(msgFailLog,example);
                }
            } catch (Exception ex) {
                FeiShuUtil.sendMsg(String.format("mengwang通道短信发送后回调更新本地短信日志出错：%s",ex.getMessage()));
                log.error("mengwang通道短信发送后回调更新本地短信日志出错：{}",ex);
            }
        });
    }

}
